home *** CD-ROM | disk | FTP | other *** search
- /*
- 94/01/09 aih
- - added memory resource for setting up memory
- - background notification options are loaded from a resource
-
- 94/01/06 aih
- - removed initialization of THINK C's console since I now provide
- my own debug window
-
- 94/01/04 aih
- - segments no longer need to be explicitely locked
-
- 93/12/31 aih
- - moved VBL task into separate file
-
- 93/12/27 aih
- - apple menu is enabled for some modal dialogs so ModalDialog will handle
- editing commands
-
- 93/12/15 aih
- - as recommended in Memory, p1-39, changed stack allocation from
- an absolute size to a relative increase, so should work on all machines
-
- 93/11/30 aih
- - added VBL task to fill location zero with an odd integer
-
- 93/10/29 aih
- - when profiling, the segment containing the profile library is locked
- to prevent an ugly crash due to unbounded recursion via the LoadSeg patch
-
- 93/10/23 aih
- - removed some initializations which are no longer needed
-
- 93/03/23 AIH
- - Segments are unloaded after initialization
-
- 93/03/19 AIH
- - Segments are unloaded and the scrap is loaded when the application
- terminates
- - Toolbox and master pointers are initialized before other initializations
- and before other segments are loaded
- - Moved pre-system 7.0 file open/print from HighLevelEventLib.c
-
- 93/03/17 AIH
- - Added menu table parameter
-
- 93/03/06 AIH
- - Added thresholds for memory warnings
-
- 92/02/29 AIH
- - Added initialization for periodic event library
-
- 92/02/27 AIH
- - The draw library no longer needs to be initialized
-
- 91/05/26 AIH
- - Using library resources
-
- 91/05/14 AIH
- - Added window menu library
-
- 91/05/12 AIH
- - Made some small improvements; added Screen Library
-
- 91/05/05 AIH
- - Added function to get the creator of the current application
-
- 91/04/22 Ari Halberstadt (AIH)
- - Created this library */
-
- #if PROFILE && defined(THINK_C)
- #include <profile.h>
- #include <console.h>
- #endif
-
- #include <stdio.h>
- #include <limits.h>
- #include "AlertFakeLib.h"
- #include "AlertLib.h"
- #include "ApplicationLib.h"
- #include "ApplicationPreferencesLib.h"
- #include "DialogLib.h"
- #include "DrawLib.h"
- #include "HighLevelEventLib.h"
- #include "KeyLib.h"
- #include "MacLib.h"
- #include "LowMemLib.h"
- #include "MemoryLib.h"
- #include "MenuLib.h"
- #include "NotifyLib.h"
- #include "ResourceConstantsLib.h"
- #include "ResourceLib.h"
- #include "ResourceTypeLib.h"
- #include "ScreenLib.h"
- #include "SegmentLib.h"
- #include "VBLTaskLib.h"
-
- /* get the creator of the current application */
- OSType AppCreator(void)
- {
- FileType fp;
- Handle bndl;
- OSType creator = '????';
-
- FileSetRef(&fp, MacAppRefNum());
- creator = FileCreator(&fp);
- if (creator == 'KAHL' || creator == 'RSED') {
- /* when debugging in THINK C use the 'BNDL' resource */
- bndl = ResGet('BNDL', 128);
- creator = *(OSType *) *bndl;
- }
- return(creator);
- }
-
- /* initialize profiler */
- static void ProfileInit(void)
- {
- #if PROFILE && defined(THINK_C)
- console_options.nrows = 10;
- cecho2file("console", 0, stdout);
- InitProfile(1024, 200);
- _profile = true;
- _trace = false;
- #endif
- }
-
- /* Open or print files using pre-system 7.0 method. Based on listing in
- "Inside Macintosh: Files", p1-35. Returns true if application should
- enter main event loop. */
- Boolean AppFilesInit(void)
- {
- short nopened = 0;
- volatile short n = 0;
- volatile short i = 1;
- volatile short job = 0;
- AppFile afile;
- FileType file;
-
- TRY {
- CountAppFiles(&job, &n);
- while (i <= n) {
- GetAppFiles(i, &afile);
- FileSetWD(&file, afile.vRefNum, p2cstr(afile.fName));
- if (job == appOpen) {
- HLEventOpenOne(&file);
- nopened++;
- }
- else if (job == appPrint)
- HLEventPrintOne(&file);
- ClrAppFiles(i);
- ++i;
- }
- if (job != appPrint && nopened == 0 && ! MacHasAppleEvents())
- HLEventOpenApplication();
- else if (job == appPrint)
- HLEventPrintOne(NULL);
- } CATCH {
- if (++i <= n) /* skip file */
- RETRY;
- if (job == appPrint)
- HLEventPrintOne(NULL);
- } ENDTRY;
- return(job == appOpen);
- }
-
- /* create the menu bar */
- static void MenuInit(void)
- {
- MenuBarGet(RLMBAR);
- }
-
- /* initialize the application heap */
- static void HeapInit(size_t stack, short masters)
- {
- SetApplLimit(GetApplLimit() - stack);
- MaxApplZone();
- while (masters-- > 0)
- MoreMasters();
- }
-
- /* resume procedure installed with InitDialogs */
- static pascal void Resume(void)
- {
- ExitToShell();
- }
-
- /* initialize managers */
- static void ManagersInit(void)
- {
- EventRecord event;
- CursHandle crsr;
- short i;
-
- /* standard initializations */
- InitGraf((Ptr) &thePort);
- InitFonts();
- InitWindows();
- InitMenus();
- TEInit();
- InitDialogs(Resume);
- FlushEvents(everyEvent, 0);
-
- /* so first window will be frontmost */
- for (i = 0; i < 4; i++)
- EventAvail(everyEvent, &event);
-
- /* SetCursor won't move or purge memory */
- crsr = GetCursor(watchCursor);
- if (crsr && *crsr)
- SetCursor(*crsr);
- }
-
- /* check the system version */
- static void VersionCheck(short version)
- {
- Str255 str;
- SysEnvRec env;
-
- (void) SysEnvirons(curSysEnvVers, &env);
- if (env.systemVersion < version) {
- GetIndString(str, RLS_ALERT, RLS_ALERT_SYSTEM);
- AlertFakeOk(str, stopIcon);
- FailOSErr(userCanceledErr);
- }
- }
-
- /* initialize the libraries */
- static void LibrariesInit(const ApplicationSettingsType *app)
- {
- AlertOptionsType options;
-
- /***
- *** WARNING: The code up to and including the call to VersionCheck()
- *** must work with all versions of system software. The
- *** code up to and including the call to MemInit
- *** must be in the main segment.
- ***/
-
- VBLInit();
- HeapInit(app->stack, app->masters);
- SegmentsInit();
- ManagersInit();
- AlertFakeInit();
- VersionCheck(app->version);
- MemInit(app->cushion, app->reserve);
- ScreenInit();
- options = **(AlertOptionsHandle) ResGet(RES_NMOP_TYPE, RLNMOP_BACKGROUND);
- AlertOptionsSet(&options);
- MenuInit();
- HLEventInit();
- ProfileInit();
- DlgPreload('ALRT', RLA_OK);
- AppPrefsRead(AppPrefs());
- }
-
- /* called on exception */
- void AppFailed(void)
- {
- const char *explanation = gException.explanation;
- CStr255 s;
- char *p = s;
-
- if (FailReason() != userCanceledErr) {
- /* can't use strcpy since may be in different segment */
- while (*explanation) *p++ = *explanation++; *p = 0;
- AlertFakeFailed(FailReason(), c2pstr(s));
- }
- }
-
- /* initialize the application */
- void AppBegin(void)
- {
- ApplicationSettingsType app;
- Handle rsrc;
-
- TRY {
- rsrc = GetResource(RES_APP_TYPE, RLAPP_SETTINGS);
- FailNILRes(rsrc);
- app = **(ApplicationSettingsHandle) rsrc;
- LibrariesInit(&app);
- if (MemContiguousSize() < app.minimum) {
- UnloadScrap();
- SegmentsUnload();
- if (MemContiguousSize() < app.minimum)
- FailOSErr(memFullErr);
- }
- } CATCH {
- AppFailed();
- } ENDTRY;
- }
-
- /* call after initializing to enter main event loop */
- void AppRun(void)
- {
- TRY {
- DrawMenuBar();
- if (AppFilesInit()) {
- /* unload segments so that the segment containing the
- main event loop can be loaded and permanently
- locked at top of heap */
- SegmentsUnload();
- EventLoopMain();
- }
- } CATCH {
- AppFailed();
- } ENDTRY;
- }
-
- /* cleanup and exit */
- void AppEnd(void)
- {
- /* unload segments so there will be room for the scrap */
- #if PROFILE && defined(THINK_C)
- DumpProfile();
- #endif
- SegmentsUnload();
- LoadScrap(); /* see IM-1, p456 */
- ExitToShell(); /* also removes all of our patches */
- }
-
- void ApplicationAdjustMenu(void)
- {
- if (! WinModalHasFocus() || (FocusWindow() && WinHasDrag(FocusWindow())))
- MenuCmdEnable(CMD_APPLE);
- if (WinModalHasFocus() && MacVersion() >= 0x0700 && FrontWindow()) {
- /* In System 7.0, ModalDialog will handle editing commands in the
- Edit menu for modal dialogs. In this application, ModalDialog
- is only used indirectly, via the Standard File Package. Normally,
- all our menus are disabled if a modal window not created by this
- application is front most. To allow ModalDialog to handle editing
- commands we enable the Apple menu and the first item in the Apple
- menu if the front most window is a modal dialog with an edit text
- field and the window was not created directly by this application
- (i.e., WinInitialize was never called for the window). The System
- 7.0 behavior of ModalDialog is described in IM-VI, p3-14. */
- WindowPtr front = FrontWindow();
- if (! WinHasExtra(front) &&
- WinIsDialog(front) &&
- WinIsModal(front) &&
- ((DialogPeek) front)->editField >= 0)
- {
- MenuEnable(MenuCmdHandle(CMD_APPLE), 0, true);
- MenuEnable(MenuCmdHandle(CMD_APPLE), 1, true);
- }
- }
- if (! WinModalHasFocus())
- MenuCmdEnable(CMD_FILE);
- MenuCmdEnable(CMD_QUIT);
- }
-
- Boolean ApplicationMenu(const MenuPickType *pick)
- {
- Boolean handled = false;
-
- switch (pick->cmd) {
- case CMD_QUIT:
- HLEventQuit();
- handled = true;
- break;
- }
- return(handled);
- }
-